﻿using System;
using SlimDX.Direct2D;
using SlimDX.Direct3D11;
using SlimDX.DXGI;
using SlimMath;
using FeatureLevel = SlimDX.Direct2D.FeatureLevel;
using MapFlags = SlimDX.Direct3D11.MapFlags;

namespace JamesZhao.Engine.Graphics.Surfaces
{
    public class ColorSurface : Surface
    {
        private ShaderResourceView _inputView;
        private RenderTargetView _outputView;

        public ColorSurface(GraphicsDevice device, TextureTargetMode mode)
        {
            Device = device;
            Mode = mode;
            WidthRatio = HeightRatio = 1;
        }

        public ColorSurface(GraphicsDevice device, Texture2D texture, TextureTargetMode mode)
            : this(device, mode)
        {
            Texture = texture;
        }

        public Format Format { get; set; }

        public RenderTargetView TargetView
        {
            get { return _outputView ?? (_outputView = new RenderTargetView(Device.Device, Texture)); }
        }

        public ShaderResourceView ResourceView
        {
            get { return _inputView ?? (_inputView = new ShaderResourceView(Device.Device, Texture)); }
        }

        public override void Initialize()
        {
            if (Mode == TextureTargetMode.Raw) return;

            DestroyTexture();
            DestroyViews();

            Texture = new Texture2D(Device.Device, new Texture2DDescription
                                                       {
                                                           ArraySize = 1,
                                                           BindFlags =
                                                               CpuReadable
                                                                   ? BindFlags.None
                                                                   : BindFlags.RenderTarget | BindFlags.ShaderResource,
                                                           CpuAccessFlags =
                                                               CpuReadable
                                                                   ? CpuAccessFlags.Read
                                                                   : CpuAccessFlags.None,
                                                           Format = Format,
                                                           Width = ActualSize.Width,
                                                           Height = ActualSize.Height,
                                                           MipLevels = 1,
                                                           OptionFlags = ResourceOptionFlags.None,
                                                           SampleDescription = SampleDescription,
                                                           Usage =
                                                               CpuReadable
                                                                   ? ResourceUsage.Staging
                                                                   : ResourceUsage.Default,
                                                       });




        }

        public override void DestroyTexture()
        {
            if (Texture != null)
            {
                Texture.Dispose();
            }
            Texture = null;
        }

        public override void DestroyViews()
        {
            if (_outputView != null)
            {
                _outputView.Dispose();
            }
            if (_inputView != null)
            {
                _inputView.Dispose();
            }
            _outputView = null;
            _inputView = null;
        }

        public void DestroyResources()
        {
            DestroyViews();
            DestroyTexture();
        }
        private RenderTarget _target2D;


        public PathGeometry CreatePathGeometry()
        {
            return new PathGeometry(Device.D2DFactory);
        }
        public SolidColorBrush CreateSolidColorBrush(Color4 color4)
        {
            return new SolidColorBrush(Target2D, color4);
        }
        public RenderTarget Target2D
        {
            get
            {
                if (_target2D == null)
                {
                    var renderTargetProperties = new RenderTargetProperties
                                                     {
                                                         PixelFormat =
                                                             new PixelFormat(Texture.Description.Format,
                                                                             AlphaMode.Ignore),
                                                         Type = RenderTargetType.Hardware,
                                                         Usage = RenderTargetUsage.None,
                                                         MinimumFeatureLevel = FeatureLevel.Direct3D10
                                                     };
                    _target2D = RenderTarget.FromDXGI(Device.D2DFactory, Texture.AsSurface(), renderTargetProperties);
                }
                return _target2D;
            }
        }
    }
}